<template>
  <div class="user-container">
    <el-card class="box-card">
      <!-- 搜索区域 -->
      <search-form v-model="queryParams" @search="handleQuery" @reset="handleReset">
        <el-form-item label="关键词">
          <el-input
            v-model="queryParams.keyword"
            placeholder="用户名/昵称"
            clearable
            @keyup.enter="handleQuery"
          />
        </el-form-item>
        <el-form-item label="状态">
          <el-select v-model="queryParams.status" placeholder="请选择状态" clearable>
            <el-option label="启用" value="1" />
            <el-option label="禁用" value="0" />
          </el-select>
        </el-form-item>
      </search-form>

      <!-- 操作按钮区域 -->
      <table-toolbar
        :has-selected="selectedIds.length > 0"
        @add="handleAdd"
        @batch-delete="handleBatchDelete"
      >
        <!-- 添加自定义按钮 -->
        <template #buttons>
          <el-button
            type="success"
            :icon="RefreshRight"
            @click="handleRefresh"
          >
            刷新
          </el-button>
        </template>
      </table-toolbar>

      <!-- 表格区域 -->
      <el-table
        v-loading="loading"
        :data="list"
        :height="tableHeight"
        @selection-change="handleSelectionChange"
      >
        <el-table-column type="selection" width="55" align="center" />
        <el-table-column label="用户名" prop="username" min-width="120" show-overflow-tooltip />
        <el-table-column label="昵称" prop="nickname" min-width="120" show-overflow-tooltip />
        <el-table-column label="角色" min-width="150" show-overflow-tooltip>
          <template #default="{ row }">
            <el-tag
              v-for="role in row.roles"
              :key="role.id"
              class="role-tag"
              size="small"
            >
              {{ role.name }}
            </el-tag>
            <el-tag v-if="!row.roles?.length" type="info" size="small">无角色</el-tag>
          </template>
        </el-table-column>
        <el-table-column label="邮箱" prop="email" min-width="180" show-overflow-tooltip />
        <el-table-column label="手机号" prop="mobile" min-width="120" show-overflow-tooltip />
        <el-table-column label="状态" align="center" width="80">
          <template #default="{ row }">
            <el-switch
              v-model="row.status"
              :active-value="'1'"
              :inactive-value="'0'"
              @change="handleStatusChange(row)"
            />
          </template>
        </el-table-column>
        <el-table-column label="创建时间" prop="createTime" min-width="160" show-overflow-tooltip />
        <el-table-column label="操作" width="240" align="center" fixed="right">
          <template #default="{ row }">
            <el-button type="primary" link :icon="Edit" @click="handleUpdate(row)">
              编辑
            </el-button>
            <el-button type="primary" link :icon="Key" @click="handleRole(row)">
              角色
            </el-button>
            <el-button type="success" link :icon="Key" @click="handleResetPwd(row)">
              重置密码
            </el-button>
            <el-button
              type="danger"
              link
              :icon="Delete"
              @click="handleDelete(row)"
              v-if="row.username !== 'admin'"
            >
              删除
            </el-button>
          </template>
        </el-table-column>
      </el-table>

      <!-- 分页区域 -->
      <pagination
        v-model:page="queryParams.pageNum"
        v-model:limit="queryParams.pageSize"
        :total="total"
        @pagination="getList"
      />

      <!-- 用户表单对话框 -->
      <el-dialog
        v-model="dialog.visible"
        :title="dialog.title"
        width="500px"
        append-to-body
        @close="resetForm"
      >
        <el-form
          ref="formRef"
          :model="form"
          :rules="userRules"
          label-width="80px"
        >
          <el-form-item label="用户名" prop="username">
            <el-input
              v-model="form.username"
              placeholder="请输入用户名"
              :disabled="form.id !== undefined"
            />
          </el-form-item>
          <el-form-item label="昵称" prop="nickname">
            <el-input v-model="form.nickname" placeholder="请输入昵称" />
          </el-form-item>
          <el-form-item label="密码" prop="password" v-if="!form.id">
            <el-input
              v-model="form.password"
              type="password"
              placeholder="请输入密码"
              show-password
            />
          </el-form-item>
          <el-form-item label="邮箱" prop="email">
            <el-input v-model="form.email" placeholder="请输入邮箱" />
          </el-form-item>
          <el-form-item label="手机号" prop="mobile">
            <el-input v-model="form.mobile" placeholder="请输入手机号" />
          </el-form-item>
          <el-form-item label="角色" prop="roleIds">
            <el-select
              v-model="form.roleIds"
              multiple
              placeholder="请选择角色"
              style="width: 100%"
            >
              <el-option
                v-for="role in roleOptions"
                :key="role.id"
                :label="role.name"
                :value="role.id"
              />
            </el-select>
          </el-form-item>
          <el-form-item label="状态" prop="status">
            <el-radio-group v-model="form.status">
              <el-radio value="1">启用</el-radio>
              <el-radio value="0">禁用</el-radio>
            </el-radio-group>
          </el-form-item>
        </el-form>
        <template #footer>
          <div class="dialog-footer">
            <el-button @click="dialog.visible = false">取 消</el-button>
            <el-button type="primary" @click="submitForm" :loading="submitLoading">
              确 定
            </el-button>
          </div>
        </template>
      </el-dialog>

      <!-- 分配角色对话框 -->
      <el-dialog
        v-model="roleDialog.visible"
        title="分配角色"
        width="500px"
        append-to-body
      >
        <el-form :model="roleForm" label-width="80px">
          <el-form-item label="用户名">
            <el-input v-model="roleForm.username" disabled />
          </el-form-item>
          <el-form-item label="角色">
            <el-select
              v-model="roleForm.roleIds"
              multiple
              placeholder="请选择角色"
              style="width: 100%"
            >
              <el-option
                v-for="role in roleOptions"
                :key="role.id"
                :label="role.name"
                :value="role.id"
              />
            </el-select>
          </el-form-item>
        </el-form>
        <template #footer>
          <div class="dialog-footer">
            <el-button @click="roleDialog.visible = false">取 消</el-button>
            <el-button type="primary" @click="submitRoleForm" :loading="submitLoading">
              确 定
            </el-button>
          </div>
        </template>
      </el-dialog>
    </el-card>
  </div>
</template>

<script setup lang="ts">
import { ref, reactive, onMounted, onBeforeUnmount } from "vue";
import { useCrud } from "@/hooks/useCrud";
import {
  getUserList,
  addUser,
  updateUser,
  deleteUser,
  batchDeleteUser,
  assignUserRoles,
  resetPassword
} from "@/api/system/user";
import { getRoleList } from "@/api/system/role";
import { Edit, Delete, Key, RefreshRight } from "@element-plus/icons-vue";
import { ElMessage, ElMessageBox } from "element-plus";
import SearchForm from "@/components/base/SearchForm.vue";
import TableToolbar from "@/components/base/TableToolbar.vue";
import Pagination from "@/components/base/Pagination.vue";
import type { Role } from "@/api/system/types";

// 角色选项
const roleOptions = ref<Role[]>([]);

// 加载角色列表
const loadRoleOptions = async () => {
  try {
    const res = await getRoleList();
    if (res.data) {
      roleOptions.value = res.data.filter(role => role.status === '1'); // 只显示启用的角色
    }
  } catch (error) {
    console.error("Failed to load roles:", error);
    ElMessage.error("加载角色列表失败");
  }
};

// 表单校验规则
const userRules = {
  username: [
    { required: true, message: "请输入用户名", trigger: "blur" },
    { min: 3, max: 20, message: "长度在 3 到 20 个字符", trigger: "blur" },
  ],
  nickname: [{ required: true, message: "请输入昵称", trigger: "blur" }],
  password: [
    { required: true, message: "请输入密码", trigger: "blur" },
    { min: 6, max: 20, message: "长度在 6 到 20 个字符", trigger: "blur" },
  ],
  email: [
    { required: true, message: "请输入邮箱", trigger: "blur" },
    { type: "email", message: "请输入正确的邮箱地址", trigger: "blur" },
  ],
  mobile: [
    { required: true, message: "请输入手机号", trigger: "blur" },
    {
      pattern: /^1[3-9]\d{9}$/,
      message: "请输入正确的手机号",
      trigger: "blur",
    },
  ],
  roleIds: [{ required: true, message: "请选择角色", trigger: "change" }],
};

// 使用通用 CRUD hooks
const {
  queryParams,
  loading,
  list,
  total,
  selectedIds,
  dialog,
  formRef,
  form,
  getList,
  handleQuery,
  handleReset,
  handleSelectionChange,
  handleAdd,
  handleUpdate,
  submitForm,
  handleDelete,
  handleBatchDelete,
} = useCrud({
  listApi: getUserList,
  addApi: addUser,
  updateApi: updateUser,
  deleteApi: deleteUser,
  batchDeleteApi: batchDeleteUser,
  formRules: userRules,
  defaultForm: {
    username: "",
    nickname: "",
    password: "",
    email: "",
    mobile: "",
    status: "1",
    roleIds: [],
  },
});

// 提交状态
const submitLoading = ref(false);

// 角色分配对话框
const roleDialog = reactive({
  visible: false,
});

// 角色分配表单
const roleForm = reactive({
  id: undefined as number | undefined,
  username: "",
  roleIds: [] as number[],
});

// 处理分配角色
const handleRole = (row: any) => {
  roleForm.id = row.id;
  roleForm.username = row.username;
  roleForm.roleIds = row.roleIds || [];
  roleDialog.visible = true;
};

// 提交角色分配
const submitRoleForm = async () => {
  if (!roleForm.id) return;
  
  try {
    submitLoading.value = true;
    await assignUserRoles(roleForm.id, roleForm.roleIds);
    ElMessage.success("分配角色成功");
    roleDialog.visible = false;
    getList();
  } catch (error: any) {
    ElMessage.error(error.message || "分配角色失败");
  } finally {
    submitLoading.value = false;
  }
};

// 处理状态变更
const handleStatusChange = async (row: any) => {
  try {
    await updateUser({
      id: row.id,
      status: row.status,
    });
    ElMessage.success("修改状态成功");
  } catch (error: any) {
    row.status = row.status === "1" ? "0" : "1";
    ElMessage.error(error.message || "修改状态失败");
  }
};

// 处理重置密码
const handleResetPwd = async (row: any) => {
  try {
    await ElMessageBox.confirm("确认要重置该用户的密码吗？", "警告", {
      type: "warning",
    });
    await resetPassword(row.id);
    ElMessage.success("重置密码成功");
  } catch (error: any) {
    if (error !== "cancel") {
      ElMessage.error(error.message || "重置密码失败");
    }
  }
};

// 刷新列表
const handleRefresh = () => {
  getList();
};

// 重置表单
const resetForm = () => {
  if (formRef.value) {
    formRef.value.resetFields();
  }
  form.value = {
    username: "",
    nickname: "",
    password: "",
    email: "",
    mobile: "",
    status: "1",
    roleIds: [],
  };
};

// 表格高度自适应
const tableHeight = ref(500);

const calculateTableHeight = () => {
  const windowHeight = window.innerHeight;
  const otherHeight = 300;
  tableHeight.value = windowHeight - otherHeight;
};

onMounted(() => {
  getList();
  loadRoleOptions();
  calculateTableHeight();
  window.addEventListener("resize", calculateTableHeight);
});

onBeforeUnmount(() => {
  window.removeEventListener("resize", calculateTableHeight);
});
</script>

<style lang="scss" scoped>
.user-container {
  height: 100%;

  .box-card {
    height: 100%;
    display: flex;
    flex-direction: column;

    :deep(.el-card__body) {
      flex: 1;
      overflow: hidden;
      display: flex;
      flex-direction: column;
    }
  }

  .role-tag {
    margin-right: 4px;
    margin-bottom: 4px;
  }

  .el-table {
    flex: 1;
  }

  .pagination-container {
    margin-top: 20px;
    display: flex;
    justify-content: flex-end;
  }
}

// 响应式布局
@media screen and (max-width: 768px) {
  .user-container {
    .el-table {
      :deep(.el-table__cell) {
        padding: 8px 0;
      }
    }

    .pagination-container {
      :deep(.el-pagination) {
        .el-pagination__sizes {
          display: none;
        }
      }
    }
  }
}
</style>
